package org.summerframework.component.security.captcha;

import org.summerframework.component.security.context.RequestContextFactory;
import org.summerframework.core.captcha.NumberCaptcha;
import com.wf.captcha.utils.CaptchaUtil;
import lombok.AllArgsConstructor;
import lombok.Getter;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.*;
import java.io.IOException;

/**
 * 图形验证码工具类
 * Created by 王帆 on 2018-07-27 上午 10:08.
 * {@code}
 * Captcha.build().width(130).height(48).len(5).sessionKey(key).toBuilder().out()
 */
@AllArgsConstructor
public class Captcha {
    @Getter
    private com.wf.captcha.base.Captcha captcha;

    private String sessionKey;

    private Captcha() {
    }

    public static CaptchaBuild build() {
        return new CaptchaBuild();
    }

    /**
     * 验证
     *
     * @param code       验证码
     * @param sessionKey sessionKey
     * @return 是否通过
     */
    public static boolean ver(String code, String sessionKey) {
        if (code != null) {
            final HttpSession session = RequestContextFactory.getCurrentContext().getSession();
            String captcha = (String) session.getAttribute(sessionKey);
            final boolean equals = code.trim().toLowerCase().equals(captcha);

            if (equals) {
                session.removeAttribute(sessionKey);
            }

            return equals;
        }
        return false;
    }

    /**
     * 输出到response中
     *
     * @throws IOException 导出异常
     */
    public void out() throws IOException {
        if (sessionKey != null) {
            final HttpServletResponse response = RequestContextFactory.getCurrentContext().getResponse();
            final HttpServletRequest request = RequestContextFactory.getCurrentContext().getRequest();
            CaptchaUtil.setHeader(response);
            request.getSession().setAttribute(sessionKey, captcha.text().toLowerCase());
            captcha.out(response.getOutputStream());
        }
    }

    public static class CaptchaBuild {
        private static final String SESSION_KEY = "captcha";
        private static final int DEFAULT_LEN = 4;  // 默认长度
        private static final int DEFAULT_WIDTH = 130;  // 默认宽度
        private static final int DEFAULT_HEIGHT = 48;  // 默认高度
        private static final Font DEFAULT_FONT = new Font("Verdana", Font.PLAIN, 32);  // 默认高度

        private CaptchaBuild() {
        }

        private int width = DEFAULT_WIDTH;

        private int height = DEFAULT_HEIGHT;

        private int len = DEFAULT_LEN;

        private String sessionKey = SESSION_KEY;

        private Font font = DEFAULT_FONT;

        private Boolean test;

        private com.wf.captcha.base.Captcha captcha;

        /**
         * @param width 宽度
         * @return build
         */
        public CaptchaBuild width(int width) {
            this.width = width;
            return this;
        }

        /**
         *
         * @param height 高度
         * @return
         */
        public CaptchaBuild height(int height) {
            this.height = height;
            return this;
        }

        /**
         *
         * @param len 长度
         * @return
         */
        public CaptchaBuild len(int len) {
            this.len = len;
            return this;
        }

        /**
         *
         * @param sessionKey 存储的sessionKey
         * @return
         */
        public CaptchaBuild sessionKey(String sessionKey) {
            this.sessionKey = sessionKey;
            return this;
        }

        /**
         *
         * @param font 字体
         * @return
         */
        public CaptchaBuild font(Font font) {
            this.font = font;
            return this;
        }

        /**
         * @param test 是否测试
         * @return
         */
        public CaptchaBuild test(Boolean test) {
            this.test = test;
            return this;
        }

        public CaptchaBuild captcha(com.wf.captcha.base.Captcha captcha) {
            this.captcha = captcha;
            return this;
        }

        public Captcha toBuilder() {
            if (captcha == null) {
                captcha = new NumberCaptcha(width, height, len, font, test);
            }

            return new Captcha(captcha, sessionKey);
        }
    }
}
